/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package pkgPrincipal;

import jgame.JGObject;

/**
 *
 * @author Gravufo
 */
public class Mouton extends JGObject
{

    /**
     * Enum qui permet de definir l'etat du mouton (direction ainsi qu'image)
     */
    public enum Direction
    {

        sheepLeft, sheepRight, sheepJetPackLeft,
        sheepJetPackRight, defaut
    };
    /**
     * Variable contenant la direction et l'etat present du mouton
     */
    private Direction direction;
    /**
     * Contient la vitesse normale en X du mouton
     */
    private final double vitesseNormaleX = 5.0;
    /**
     * Contient la vitesse normale en Y du mouton
     */
    private final double vitesseNormaleY = 7.5;
    /**
     * Contient la vitesse en Y du mouton lorsqu'il a le JetPack
     */
    private final double vitesseJetPackY = 15.0;
    /**
     * Contient la vitesse en Y du mouton lorsqu'il saute sur un ressort
     */
    private final double vitesseRessortY = 15.0;
    /**
     * Acceleration gravitationnelle
     */
    private final double acceleration = 9.9 / 60;
    /**
     * Contient l'etat du mouton (vivant = true; mort = false)
     */
    private boolean alive = true;
    /**
     * Permet de savoir si le mouton est en mode JetPack ou non
     */
    private boolean jetPack = false;

    /**
     * Constructeur de mouton
     * @param objectName Nom a utiliser pour identifier le mouton
     * @param x Position en x
     * @param y Position en y
     * @param direction Definit l'etat initial du mouton
     */
    public Mouton(String objectName, double x, double y, Direction direction)
    {
        super(objectName, true, x, y, 1, direction.toString());
        this.direction = direction;

        // On applique une certaine direction de depart
        xdir = 0;
        ydir = 1;
    }

    /**
     * Methode qui definit le mouvement du mouton
     */
    @Override
    public void move()
    {
        // Si le mouton est dans l'ecran de jeu
        if (this.isInView(0, 644))
        {
            // Si aucune fleche n'est appuyee
            if (direction == direction.defaut)
            {
                // S'il a une vitesse et qu'il bouge dans cette vitesse
                if (xspeed > 0 && xdir != 0)
                {
                    // On le reduit graduellement
                    xspeed -= 0.4;
                }
                else
                {
                    // Il a atteint le minimum, alors on l'arrete
                    xdir = 0;

                    // Et on remet sa vitesse a la vitesse normale
                    xspeed = vitesseNormaleX;
                }
            }

            // Si on l'a trop accelere, on le ralentit
            if (xspeed >= 6.0)
            {
                xspeed = vitesseNormaleX;
            }
        }
        // S'il est hors de l'ecran de jeu
        else
        {
            // Si le mouton atteint un des cotes de l'ecran
            if (this.y != (Jeu.dernierOffset + 645))
            {
                // On le repositionne de l'autre cote, selon le cote ou il est
                // presentement
                if (xdir == -1)
                {
                    this.setPos(355, this.y);
                }
                else if (xdir == 1)
                {
                    this.setPos(-5, this.y);
                }
            }
        }

        // S'il a un JetPack en ce moment
        if (jetPack)
        {
            // On applique la vitesse du JetPack
            yspeed = vitesseJetPackY;
            ydir = -1;

        }
        // Sinon si le mouton va vers le haut
        else if (ydir < 0)
        {
            // On utilise un BoundingBox sur toute l'image pour des collisions
            // de tous les cotes
            setBBox(5, 5, 30, 70);

            // On le ralentit selon l'acceleration gravitationnelle
            yspeed -= acceleration;

            // Si sa vitesse atteint un minimum
            if (yspeed <= 0.5)
            {
                // On change sa direction pour qu'il redescende
                ydir = 0;
            }
        }
        // Sinon si le mouton va vers le bas
        else if (ydir > 0)
        {
            // On l'accelere selon l'acceleration gravitationnelle
            yspeed += acceleration;
        }
        // Sinon si le mouton ne va dans aucune direction en y
        else if (ydir == 0)
        {
            // On applique un BoundingBox seulement sur le bas de l'image
            // pour faire des collisions uniquement par le bas sur les plateformes
            setBBox(5, 72, 40, 1);

            // On lui applique une direction vers le bas
            ydir = 1;
        }
    }

    @Override
    /**
     * Methode qui gere les collisions du mouton
     */
    public void hit(JGObject objet)
    {
        // Si l'objet qui a frappe le mouton est une plateforme
        if (objet instanceof Plateforme)
        {
            // Si le mouton va vers le bas et est vivant
            if (ydir > 0 && alive)
            {

                // On change sa direction (il rebondit sur une plateforme)
                ydir = -ydir;

                eng.playAudio("jump");

                // On ramene sa vitesse en Y a la normale
                yspeed = vitesseNormaleY;
            }
        }
        // Sinon si l'objet qui a frappe le mouton est un ressort
        else if (objet instanceof Ressort)
        {
            Ressort ressort = (Ressort) objet;

            // Si le mouton va vers le bas et est vivant
            if (ydir > 0 && alive)
            {
                // On change sa direction (il rebondit sur une plateforme)
                ydir = -ydir;

                // On ramene sa vitesse en Y a la normale
                yspeed = vitesseRessortY;

                // On change l'image du ressort pour l'ouvrir
                ressort.ouvrirRessort();
            }
        }
    }

    /**
     * Permet de changer l'etat du mouton selon le mouvement et son etat precedent
     * @param objetSpecial Permet de choisir si on doit changer l'image du mouton
     */
    public void changerDirection(Direction direction)
    {
        // On sauvegarde la direction obtenue
        this.direction = direction;

        // Selon la direction
        switch (direction)
        {
            case sheepLeft: // Lorsque le mouton va vers la gauche
                xdir = -1;
                this.setGraphic("sheepLeft");
                break;
            case sheepRight: // Lorsque le mouton va vers la droite
                xdir = 1;
                this.setGraphic("sheepRight");
                break;
            case sheepJetPackLeft: // Lorsque le mouton va vers la gauche avec un JetPack
                xdir = -1;
                this.setGraphic("sheepJetPackLeft");
                break;
            case sheepJetPackRight: // Lorsque le mouton va vers la droite avec un JetPack
                xdir = 1;
                this.setGraphic("sheepJetPackRight");
                break;
            case defaut: // Lorsqu'aucun bouton n'est appuye
                //setGraphic("sheepRight");
                break;
        }

        // Si la vitesse du mouton est petite est que le mouton bouge
        if (xspeed < 15 && xdir != 0)
        {
            // On l'accelere selon la longueur qu'on tient le bouton
            xspeed += 0.2;
        }
    }

    /**
     * Methode qui applique les procedures lorsque le mouton meurt
     */
    public void die()
    {
        // Mettre l'image du mouton mort
        setImage("sheepDead");

        // Changer sa direction pour qu'il tombe tout droit
        ydir = 1;
        xdir = 0;

        // On dit que le mouton est mort pour empecher toute autre action
        alive = false;

        // On avertit l'Engine que la partie est finie
        eng.setGameState("End");
    }

    /**
     * @return Direction/etat du mouton
     */
    public Direction getDirection()
    {
        return direction;
    }

    /**
     * @return true si le mouton a un jet pack, false sinon
     */
    public boolean isJetpack()
    {
        return jetPack;
    }

    /**
     * Permet d'appliquer un jet pack au mouton
     * @param jetpack booleen qui permet de savoir si le mouton a un jet pack
     */
    public void setJetpack(boolean jetpack)
    {
        this.jetPack = jetpack;
    }

    /**
     * Permet de connaitre l'etat du mouton
     * @return true si le mouton est vivant, faux sinon
     */
    @Override
    public boolean isAlive()
    {
        return alive;
    }

    /**
     * Permet de tuer le mouton
     * @param Alive booleen qui contient l'etat de vie du mouton
     */
    public void setAlive(boolean Alive)
    {
        this.alive = Alive;
    }
}
